package com.abiao.shop.service;

import com.abiao.shop.dao.UserDao;
import com.abiao.shop.exception.GlobalException;
import com.abiao.shop.vojo.LoginVo;
import com.abiao.shop.pojo.User;
import com.abiao.shop.redis.RedisService;
import com.abiao.shop.redis.UserKey;
import com.abiao.shop.result.CodeMsg;
import com.abiao.shop.util.MD5Util;
import com.abiao.shop.util.UUIDUtil;
import io.netty.util.internal.StringUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletResponse;

/**
 * @Description: UserService    用户服务类
 * @Author: AB
 * @Date: 2021-07-09
 * @Version:v1.0
 */
@Service
public class UserService {

    public static final String COOKIE_NAME_TOKEN = "token";

    @Autowired
    UserDao userDao;
    @Autowired
    RedisService redisService;

    //根据id获取用户信息
    public User getById(long id){
        //取缓存
        User user = redisService.get(UserKey.getByID,""+id,User.class);
        if (user != null){
            return user;
        }
        //取数据库
        user = userDao.getById(id);
        if (user!=null){
            redisService.set(UserKey.getByID,""+id,user);
        }
        return user;
    }
    //根据用户名获取用户信息
    public User getByUserName(String userName){
        //取缓存
        User user = redisService.get(UserKey.getByName,userName,User.class);
        if (user != null){
            return user;
        }
        //取数据库
        user = userDao.getByUserName(userName);
        if (user!=null){
            redisService.set(UserKey.getByName,userName,user);
        }
        return user;
    }

    //更改密码
    public Boolean updatePassword(Long userId,String formPass,String token){
        //取数据
        User user = this.getById(userId);
        if(user == null){
            throw new GlobalException(CodeMsg.USER_NOT_EXIST);
        }
        //更新数据库
        User newUser = new User();
        newUser.setId(userId);
        newUser.setPassword(MD5Util.formPassToDBPass(formPass,user.getSalt()));
        userDao.updatePass(newUser);
        //处理缓存
        redisService.del(UserKey.getByID,""+userId);
        user.setPassword(newUser.getPassword());
        redisService.set(UserKey.token,token,user);
        return true;
    }

    //登录
    public String login(HttpServletResponse response, LoginVo loginVo){
        if (loginVo == null){
            throw new GlobalException(CodeMsg.SERVER_ERROR);
        }
        String username = loginVo.getUsername();
        String password = loginVo.getPassword();

        //获取登录用户
        User loginUser = this.getByUserName(username);
        if(loginUser == null){
            throw new GlobalException(CodeMsg.USER_NOT_EXIST);
        }

        //验证密码
        String dbPass = loginUser.getPassword();
        String dbSalt = loginUser.getSalt();
        String calcPass = MD5Util.formPassToDBPass(password,dbSalt);

        if (!calcPass.equals(dbPass)){
            throw new GlobalException(CodeMsg.PASSWORD_ERROR);
        }
        //生成cookie
        String token = UUIDUtil.uuid();
        this.addCookie(response,token,loginUser);
        return token;
    }

    //生成cookie，写入response返回给用户
    private void addCookie(HttpServletResponse response,String token, User user){
        //生成cookie
        redisService.set(UserKey.token,token,user);    //token存入redis（刷新有效期）
        Cookie cookie = new Cookie(COOKIE_NAME_TOKEN,token);    //生成cookie
        cookie.setMaxAge(UserKey.token.expireSeconds());        //过期时间默认两天
        cookie.setPath("/");        //设定路径为根目录
        response.addCookie(cookie);     //cookie写入response中
    }

    //根据cookie的token从redis中取出user实体
    public User getByToken(HttpServletResponse response, String token) {
        if (StringUtil.isNullOrEmpty(token)){
            return null;
        }
        User user = redisService.get(UserKey.token,token,User.class);
        //延长cookie有效期
        if (user!=null){
            addCookie(response,token,user);
        }
        return user;
    }
}
